package 反射.获取类的成员方法;

import 反射.获取类的成员变量.Cat;

import java.lang.reflect.Method;

public class Test {
    public static void main(String[] args) throws Exception {
        // Class提供了从类中获取成员方法的API
        // 方法:
        // 1. Method[] getMethods(): 获取类的全部成员方法 (只能获取public修饰的)
        // 2. Method[] getDeclaredMethods(): 获取类的全部成员方法 (只要存在就能拿到)
        // 3. Method getMethod(String name, Class<?>... parameterTypes): 获取类的某个成员方法 (只能获取public修饰的)
        // 4. Method getDeclaredMethod(String name, Class<?>... parameterTypes): 获取类的某个成员方法 (只要存在就能拿到)

        // 1. 发射第一步, 先得到Class对象
        Class c = Cat.class;
        // 2. 获取类的全部成员方法
        Method[] methods = c.getMethods(); // 只能访问public
        Method[] methods1 = c.getDeclaredMethods(); // 都可以访问
        // 3. 遍历这个数组中的每个方法对象
        for (Method method : methods1) {
            System.out.println(method.getName() + "----->" + method.getParameterCount() + "---->" + method.getReturnType());
        }
        // 4. 获取某个方法对象
        Method run = c.getDeclaredMethod("run");// 拿run方法, 无参数的
        System.out.println(run.getName() + "----->" + run.getParameterCount() + "---->" + run.getReturnType());

        Method eat = c.getDeclaredMethod("eat", String.class);
        System.out.println(eat.getName() + "----->" + eat.getParameterCount() + "---->" + eat.getReturnType());

        // 成员方法的作用: 依然是执行
        // 方法:
        // 1. public Object invoke(Object obj, Object...args): 触发某个对象的该方法执行
        // 2. public void setAccessible(boolean flag): 设置为true, 表示禁止检查访问控制

        Cat cat = new Cat();
        run.setAccessible(true); // 表示禁止访问权限 (也就是无视private访问, 叫做暴力反射)
        Object invoke1 = run.invoke(cat); // 无参
       // Object invoke2 = eat.invoke(cat, "鱼儿");
        System.out.println(invoke1);
        //System.out.println(invoke2);

        // 不知道为啥, 会报错

    }
}
